|
1
|
|
|
import { A_START_CHAR, B_START_CHAR, C_START_CHAR, A_CHARS, B_CHARS, C_CHARS } from './constants'; |
|
2
|
|
|
|
|
3
|
|
|
// Match Set functions |
|
4
|
|
|
const matchSetALength = (string) => string.match(new RegExp(`^${A_CHARS}*`))[0].length; |
|
5
|
|
|
const matchSetBLength = (string) => string.match(new RegExp(`^${B_CHARS}*`))[0].length; |
|
6
|
|
|
const matchSetC = (string) => string.match(new RegExp(`^${C_CHARS}*`))[0]; |
|
7
|
|
|
|
|
8
|
|
|
// CODE128A or CODE128B |
|
9
|
|
|
function autoSelectFromAB(string, isA){ |
|
10
|
|
|
const ranges = isA ? A_CHARS : B_CHARS; |
|
11
|
|
|
const untilC = string.match(new RegExp(`^(${ranges}+?)(([0-9]{2}){2,})([^0-9]|$)`)); |
|
12
|
|
|
|
|
13
|
|
|
if (untilC) { |
|
14
|
|
|
return ( |
|
15
|
|
|
untilC[1] + |
|
16
|
|
|
String.fromCharCode(204) + |
|
17
|
|
|
autoSelectFromC(string.substring(untilC[1].length)) |
|
18
|
|
|
); |
|
19
|
|
|
} |
|
20
|
|
|
|
|
21
|
|
|
const chars = string.match(new RegExp(`^${ranges}+`))[0]; |
|
22
|
|
|
|
|
23
|
|
|
if (chars.length === string.length) { |
|
24
|
|
|
return string; |
|
25
|
|
|
} |
|
26
|
|
|
|
|
27
|
|
|
return ( |
|
28
|
|
|
chars + |
|
29
|
|
|
String.fromCharCode(isA ? 205 : 206) + |
|
30
|
|
|
autoSelectFromAB(string.substring(chars.length), !isA) |
|
31
|
|
|
); |
|
32
|
|
|
} |
|
33
|
|
|
|
|
34
|
|
|
// CODE128C |
|
35
|
|
|
function autoSelectFromC(string) { |
|
36
|
|
|
const cMatch = matchSetC(string); |
|
37
|
|
|
const length = cMatch.length; |
|
38
|
|
|
|
|
39
|
|
|
if (length === string.length) { |
|
40
|
|
|
return string; |
|
41
|
|
|
} |
|
42
|
|
|
|
|
43
|
|
|
string = string.substring(length); |
|
44
|
|
|
|
|
45
|
|
|
// Select A/B depending on the longest match |
|
46
|
|
|
const isA = matchSetALength(string) >= matchSetBLength(string); |
|
47
|
|
|
return cMatch + String.fromCharCode(isA ? 206 : 205) + autoSelectFromAB(string, isA); |
|
48
|
|
|
} |
|
49
|
|
|
|
|
50
|
|
|
// Detect Code Set (A, B or C) and format the string |
|
51
|
|
|
export default (string) => { |
|
52
|
|
|
let newString; |
|
53
|
|
|
const cLength = matchSetC(string).length; |
|
54
|
|
|
|
|
55
|
|
|
// Select 128C if the string start with enough digits |
|
56
|
|
|
if (cLength >= 2) { |
|
57
|
|
|
newString = C_START_CHAR + autoSelectFromC(string); |
|
58
|
|
|
} else { |
|
59
|
|
|
// Select A/B depending on the longest match |
|
60
|
|
|
const isA = matchSetALength(string) > matchSetBLength(string); |
|
61
|
|
|
newString = (isA ? A_START_CHAR : B_START_CHAR) + autoSelectFromAB(string, isA); |
|
62
|
|
|
} |
|
63
|
|
|
|
|
64
|
|
|
return newString.replace( |
|
65
|
|
|
/[\xCD\xCE]([^])[\xCD\xCE]/, // Any sequence between 205 and 206 characters |
|
66
|
|
|
(match, char) => String.fromCharCode(203) + char |
|
67
|
|
|
); |
|
68
|
|
|
}; |
|
69
|
|
|
|